from PyQt5.QtWidgets import *
from VideoSurface import *
from PyQt5.QtMultimediaWidgets import QVideoWidget
from PyQt5.QtCore import *

class VideoWidget(QVideoWidget):
    doubleClickedItem = pyqtSignal(str)  # 创建双击信号
    def __init__(self, parent=None):
        super(VideoWidget, self).__init__(parent)
        # 当前帧QImage
        self.__image = None
        # 旋转的度数
        self.__degree = 0
        # 缩放后的宽度
        self.__scaleWidth = None
        # 缩放后的高度
        self.__scaleHeight = None
        # 缩放后的位置
        self.__posX = 0
        self.__posY = 0
        # 垂直翻转标志位
        self.__verticalFlipFlag = False
        # 水平翻转标志位
        self.__horizontalFlipFlag = False

    def resizeEvent(self, event):
        self.calculateRectAfterResize()
        if self.__degree in (-90, 90, -270, 270):
            # 交换两个变量
            self.__scaleWidth, self.__scaleHeight = self.__scaleHeight, self.__scaleWidth
        self.update()
        super(VideoWidget, self).resizeEvent(event)

    def paintEvent(self, event):
        painter = QPainter()
        painter.begin(self)
        if self.__image:
            rect = QRectF(self.__posX, self.__posY, self.__image.width(), self.__image.height())
            painter.drawImage(rect, self.__image)
        else:
            # 这里可以做视频加载动画
            pass
        painter.end()

    def calculateRectAfterResize(self):
        """调整大小后计算宽高和位置"""
        if self.__image:
            # 当前显示窗口宽高比
            widgetRatio = self.width() / self.height()
            srcRatio = self.__image.width() / self.__image.height()
            if widgetRatio >= srcRatio:
                self.__scaleWidth = srcRatio * self.height()
                self.__scaleHeight = self.height()
                self.__posX = (self.width() - self.__scaleWidth) / 2
                self.__posY = 0
            else:
                self.__scaleWidth = self.width()
                self.__scaleHeight = self.width() / srcRatio
                self.__posX = 0
                self.__posY = (self.height() - self.__scaleHeight) / 2

    def calculateRectAfterTransform(self):
        """setTransform后计算宽高和位置"""
        if self.__image:
            # 当前显示窗口宽高比
            widgetRatio = self.width() / self.height()
            srcRatio = self.__image.height() / self.__image.width()
            if widgetRatio >= srcRatio:
                self.__scaleWidth = self.height()
                self.__scaleHeight = self.height() * srcRatio
                self.__posX = (self.width() - self.__scaleHeight) / 2
                self.__posY = 0
            else:
                self.__scaleWidth = self.width() / srcRatio
                self.__scaleHeight = self.width()
                self.__posX = 0
                self.__posY = (self.height() - self.__scaleWidth) / 2

    def showImageSlot(self, img):
        """槽函数，接收图片，进行缩放和变换"""
        if self.__image is None:
            # 如果是初次接收图片，需要根据当前窗口大小计算宽高和位置
            self.__image = img
            self.calculateRectAfterResize()
            if self.__degree in (-90, 90, -270, 270):
                # 交换两个变量
                self.__scaleWidth, self.__scaleHeight = self.__scaleHeight, self.__scaleWidth
        self.__image = img
        # 缩放
        self.doScale()
        # 旋转
        self.doRotate()
        # 翻转
        self.doFlip()
        self.update()

    def doScale(self):
        """进行缩放操作"""
        if self.__scaleWidth and self.__scaleHeight:
            self.__image = self.__image.scaled(self.__scaleWidth, self.__scaleHeight)

    def doRotate(self):
        """进行旋转操作"""
        if self.__degree != 0:
            matrix = QTransform()
            matrix.rotate(self.__degree)
            self.__image = self.__image.transformed(matrix, Qt.FastTransformation)

    def doFlip(self):
        """进行翻转操作"""
        if self.__verticalFlipFlag:
            # 垂直翻转
            self.__image = self.__image.mirrored()
        elif self.__horizontalFlipFlag:
            # 水平翻转
            self.__image = self.__image.mirrored(True, False)

    def setFlip(self, direction):
        if direction == horizontalFlip:
            # 如果是水平垂直翻转，对应的标志位取反
            self.__horizontalFlipFlag = not self.__horizontalFlipFlag
        elif direction == verticalFlip:
            self.__verticalFlipFlag = not self.__verticalFlipFlag
        self.update()

    def setRotate(self, direction):
        """设置旋转角度并计算一些值"""
        if direction == rotateToLeft:
            # 如果是左右旋转，需要修改度数
            self.__degree -= 90
        elif direction == rotateToRight:
            self.__degree += 90
        # 如果旋转度数达到了+-360，归零
        if self.__degree == 360 or self.__degree == -360:
            self.__degree = 0
        self.calculateRectAfterTransform()
        if self.__degree in (0, -180, 180):
            self.__scaleWidth, self.__scaleHeight = self.__scaleHeight, self.__scaleWidth
        self.update()

    def mouseDoubleClickEvent(self,QMouseEvent):     #双击事件
        self.doubleClickedItem.emit("double clicked")


horizontalFlip = 0
verticalFlip = 1
rotateToLeft = 0
rotateToRight = 1

